package com.wxzhou.wangzhuan.entity;

import com.fasterxml.jackson.annotation.JsonFormat;
import com.wxzhou.wangzhuan.service.PayService;

import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.UUID;

/**
 * 用户提现记录实体
 */
public class UserWithdrawal {
    private Long id;

    // 提现订单号
    private String withdrawalNo;

    // 提现用户ID
    private Long userId;

    // 提现金额(单位:分)
    private BigDecimal amount;

    // 提现类型:1余额提现
    private Integer withdrawalType;

    // 提现渠道
    private Integer withdrawalChannel;

    // 账户信息(根据渠道不同存储不同信息)
    private String accountInfo;

    // 提现状态
    private Integer status;

    // 审核状态
    private Integer auditStatus;

    // 审核时间
    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
    private LocalDateTime auditTime;

    // 审核管理员ID
    private Long auditAdminId;

    // 审核备注，对外
    private String auditRemark;

    // 完成时间
    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
    private LocalDateTime completedTime;

    // 失败原因
    private String failureReason;

    // 第三方订单号
    private String thirdPartyOrderNo;

    // 备注
    private String remark;

    // 申请时间
    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
    private LocalDateTime createdAt;

    // 更新时间
    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
    private LocalDateTime updatedAt;

    private Integer paymentType;

    private Integer transAction;

    public UserWithdrawal() {
    }

    private UserWithdrawal(String withdrawalNo, Long userId, BigDecimal amount, Integer withdrawalType, Integer withdrawalChannel, Integer status, Integer auditStatus, String remark,Integer paymentType,Integer transAction) {
        this.withdrawalNo = withdrawalNo;
        this.userId = userId;
        this.amount = amount;
        this.withdrawalType = withdrawalType;
        this.withdrawalChannel = withdrawalChannel;
        this.status = status;
        this.auditStatus = auditStatus;
        this.auditAdminId = 0L;
        this.remark = remark;
        this.createdAt = LocalDateTime.now();
        this.updatedAt = LocalDateTime.now();
        this.paymentType = paymentType;
        this.transAction = transAction == null ? WithdrawTransAction.MANUAL.getCode() : transAction;
    }



    //手动提现，构造
    public static UserWithdrawal createByManual(Long userId, BigDecimal amount) {
        //TODO:工具类自动生成提现订单号，精确到纳秒级时间+nonce值6位+S_开头表示手动，MD5小写一共32位
        return new UserWithdrawal(createNo(), userId, amount, 1, WithdrawalChannel.THIRD_PARTY.getCode(), WithdrawalStatus.PROCESSING.getCode(), AuditStatus.PENDING.getCode(),  "手动",PaymentType.WEPAY.getCode(),WithdrawTransAction.MANUAL.getCode());
    }

    //自动通过，构造
    public static UserWithdrawal createByAuto(Long userId, BigDecimal amount) {
        return new UserWithdrawal(createNo(), userId, amount, 1, WithdrawalChannel.THIRD_PARTY.getCode(), WithdrawalStatus.PROCESSING.getCode(), AuditStatus.APPROVED.getCode(), "自动",PaymentType.WEPAY.getCode(),WithdrawTransAction.AUTO.getCode());
    }

    private static String createNo() {
        String withdrawalNo = PayService.md5(UUID.randomUUID() + String.valueOf(System.currentTimeMillis())).toLowerCase();
        return withdrawalNo;
    }

    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }

    public String getWithdrawalNo() {
        return withdrawalNo;
    }

    public void setWithdrawalNo(String withdrawalNo) {
        this.withdrawalNo = withdrawalNo;
    }

    public Long getUserId() {
        return userId;
    }

    public void setUserId(Long userId) {
        this.userId = userId;
    }

    public BigDecimal getAmount() {
        return amount;
    }

    public void setAmount(BigDecimal amount) {
        this.amount = amount;
    }

    public Integer getWithdrawalType() {
        return withdrawalType;
    }

    public void setWithdrawalType(Integer withdrawalType) {
        this.withdrawalType = withdrawalType;
    }

    public String getAccountInfo() {
        return accountInfo;
    }

    public void setAccountInfo(String accountInfo) {
        this.accountInfo = accountInfo;
    }

    public Integer getWithdrawalChannel() {
        return withdrawalChannel;
    }

    public void setWithdrawalChannel(Integer withdrawalChannel) {
        this.withdrawalChannel = withdrawalChannel;
    }

    public Integer getStatus() {
        return status;
    }

    public void setStatus(Integer status) {
        this.status = status;
    }

    public Integer getAuditStatus() {
        return auditStatus;
    }

    public void setAuditStatus(Integer auditStatus) {
        this.auditStatus = auditStatus;
    }

    public LocalDateTime getAuditTime() {
        return auditTime;
    }

    public void setAuditTime(LocalDateTime auditTime) {
        this.auditTime = auditTime;
    }

    public Long getAuditAdminId() {
        return auditAdminId;
    }

    public void setAuditAdminId(Long auditAdminId) {
        this.auditAdminId = auditAdminId;
    }

    public String getAuditRemark() {
        return auditRemark;
    }

    public void setAuditRemark(String auditRemark) {
        this.auditRemark = auditRemark;
    }

    public LocalDateTime getCompletedTime() {
        return completedTime;
    }

    public void setCompletedTime(LocalDateTime completedTime) {
        this.completedTime = completedTime;
    }

    public String getFailureReason() {
        return failureReason;
    }

    public void setFailureReason(String failureReason) {
        this.failureReason = failureReason;
    }

    public String getThirdPartyOrderNo() {
        return thirdPartyOrderNo;
    }

    public void setThirdPartyOrderNo(String thirdPartyOrderNo) {
        this.thirdPartyOrderNo = thirdPartyOrderNo;
    }

    public String getRemark() {
        return remark;
    }

    public void setRemark(String remark) {
        this.remark = remark;
    }

    public LocalDateTime getCreatedAt() {
        return createdAt;
    }

    public void setCreatedAt(LocalDateTime createdAt) {
        this.createdAt = createdAt;
    }

    public LocalDateTime getUpdatedAt() {
        return updatedAt;
    }

    public void setUpdatedAt(LocalDateTime updatedAt) {
        this.updatedAt = updatedAt;
    }

    public Integer getPaymentType() {
        return paymentType;
    }

    public void setPaymentType(Integer paymentType) {
        this.paymentType = paymentType;
    }

    public Integer getTransAction() {
        return transAction;
    }

    public void setTransAction(Integer transAction) {
        this.transAction = transAction;
    }
}